<script lang="ts">
    import { _ } from "svelte-i18n";
    import { BothSide } from "../BothSide";
    import { Checkbox } from "../Checkbox";
    import Icon from "../Common/Icons/Icon.svelte";
    import { Input } from "../Input";
    import { useStyle } from "../utils/useStyle";
    import ListItem from "./ListItem.svelte";
    import type { TransferListProps, TransferProps } from "./Transfer";

    const props: TransferListProps = $props();
    const style = $derived(
        useStyle(
            {},
            {
                width: props.width ? `${props.width}px` : "",
                height: props.height ? `${props.height}px` : "",
            }
        )
    );
    const data = $derived.by(() => {
        const v = props.value || [];
        const map: any = {};
        v.forEach((vv: any) => {
            map[vv] = true;
        });
        return props.store.data.filter((item: any) => {
            if (props.name === "source") {
                return !map[item.id];
            } else {
                return map[item.id];
            }
        });
    });

    const validLength = $derived.by(() => {
        let length = 0;
        data.forEach((item: any) => {
            if (!item.disabled) {
                length++;
            }
        });
        return length;
    });

    const onSelect = (data: any) => {
        props.onSelect(data, !data._checked);
        if (data._checked) {
            const key = `${props.name}Ids` as "sourceIds" | "targetIds";
            props.store[key] = [...(props.store[key] as any[]), data.id];
        } else {
            const key = `${props.name}Ids` as "sourceIds" | "targetIds";
            const arr = props.store[key];
            arr.splice(arr.indexOf(data.id), 1);
        }
    };

    const isCheckedAll = $derived.by(() => {
        const arr = props.store[`${props.name}Ids` as "sourceIds" | "targetIds"];
        if (arr.length > 0) {
            if (validLength === arr.length) {
                return true;
            } else {
                return "indeterminate";
            }
        } else {
            return false;
        }
    });

    const onCheckedAll = (checked: boolean) => {
        const ids: any[] = [];
        const items = data;
        items.forEach((item: any) => {
            props.onSelect(item, checked);
        });
        items.forEach((item: any) => {
            if (item._checked) {
                ids.push(item.id);
            }
        });
        props.store[`${props.name}Ids` as "sourceIds" | "targetIds"] = ids;
    };

    $effect(() => {
        const arr = props.store[`${props.name}Ids` as "sourceIds" | "targetIds"];
        if (arr.length) {
            props.store[`${props.name}Disabled` as "sourceDisabled" | "targetDisabled"] = false;
        } else {
            props.store[`${props.name}Disabled` as "sourceDisabled" | "targetDisabled"] = true;
        }
    });

    // 过滤
    const onFilter = (v: any) => {
        const arr = data;
        arr.forEach((item: any) => {
            const text = () => {
                if (props.render) {
                    return props.render(item);
                }
                return item.title;
            };
            props.store.data.forEach((aitem: any) => {
                if (aitem.id === item.id) {
                    aitem._hide = !text().includes(v);
                }
            });
        });
    };

    const count = $derived(data.length);
    const countInfo = $derived.by(() => {
        const arr = props.store[`${props.name}Ids` as "sourceIds" | "targetIds"];
        return arr.length ? arr.length + "/" + count : count;
    });
</script>

<div class="cm-transfer-list" {style}>
    <div class="cm-transfer-list-header">
        <BothSide>
            <div>
                <Checkbox checked={isCheckedAll} onchange={onCheckedAll} />
                <span>
                    {#if props.title}
                        {#if typeof props.title === "function"}
                            {@render props.title()}
                        {:else}
                            {props.title}
                        {/if}
                    {:else}
                        {props.name === "source" ? $_("Transfer.sourceTitle") : $_("Transfer.targetTitle")}
                    {/if}
                </span>
            </div>
            <div class="">{countInfo}</div>
        </BothSide>
    </div>
    <div class="cm-transfer-list-body">
        {#if props.filter}
            <div class="cm-transfer-filter-wrap">
                <Input size="small" oninput={onFilter}>
                    {#snippet append()}
                        <Icon icon="search" />
                    {/snippet}
                </Input>
            </div>
        {/if}
        <div class="cm-transfer-list-content">
            {#each data as item}
                <ListItem data={item} {onSelect} store={props.store} render={props.render} />
            {/each}
        </div>
    </div>
</div>
